// Module containing ImageLibary 

// delegate invoked when images are loaded
export interface IImagesLoaded {
    (): void;
}

export enum eImageID { Brick = 0, KarelNorth = 1, KarelSouth = 2, KarelWest = 3, KarelEast = 4 }

// the exported class itself
export class ImageLibrary {
  
    // singleton instance
    private static mInstance: ImageLibrary = null;

    // names of images to load
    private mImageNames: Array<string>;

    // loaded images
    private mImages: Array<HTMLImageElement>;

    // completed handler
    private mCompletedHandler: IImagesLoaded;
    private mImageLoadedCount: number;

    // constructor
    public constructor() {
        // init image array
        this.mImageNames = new Array<string>();
        this.mCompletedHandler = null;
        this.mImageLoadedCount = 0;

        // add image names
        this.mImageNames.push("/Images/brick.png");
        this.mImageNames.push("/Images/KarelNorth.png");
        this.mImageNames.push("/Images/KarelSouth.png");
        this.mImageNames.push("/Images/KarelWest.png");
        this.mImageNames.push("/Images/KarelEast.png");
    }

    // singleton instance property getter
    public static get Instance() {
        if (ImageLibrary.mInstance == null)
            ImageLibrary.mInstance = new ImageLibrary();
        return ImageLibrary.mInstance;
    }

    // returns the specified image
    public GetImage(type: eImageID): HTMLImageElement {
        return this.mImages[type];
    }

    // loads the images
    public LoadImages(completedHandler: IImagesLoaded): void {
        this.mCompletedHandler = completedHandler;
        this.mImageLoadedCount = 0;

        // iterate all image names
        var that = this;
        this.mImages = new Array<HTMLImageElement>();
        for (var i = 0; i < this.mImageNames.length; i++) {
            var imageName = this.mImageNames[i];

            // setup image and load
            var image = new Image();
            image.onload = function () {
                that.ImageLoaded();
            };
            this.mImages.push(image);
            image.src = imageName;
        }       
    }

    // image loaded event
    private ImageLoaded(): void {
        this.mImageLoadedCount++;
        
        // check the complete load
        if (this.mImageLoadedCount >= this.mImageNames.length) {
            if (this.mCompletedHandler != null) {
                this.mCompletedHandler();
            }          
        }
    }
}